#ifndef BS_THERMAL_MAIN_LOOP_CALC_H_
#define BS_THERMAL_MAIN_LOOP_CALC_H_

#include BS_FORCE_PLUGIN_IMPORT ()
#include "main_loop_calc.h"
#include BS_STOP_PLUGIN_IMPORT ()

#include "thermal_reservoir_simulator.h"
#include "thermal_fi_operator.h"


namespace blue_sky{

	template <typename strategy_t, bool is_w, bool is_g, bool is_o>
	struct thermal_main_loop_calc : public main_loop_calc <strategy_t, is_w, is_g, is_o>
	{
		typedef main_loop_calc <strategy_t, is_w, is_g, is_o>   base_t;

		typedef thermal_calc_model<strategy_t>				    thermal_calc_model_t;
		typedef smart_ptr<thermal_calc_model_t,true>		    sp_thermal_calc_model_t;		
		
		thermal_main_loop_calc (const sp_rs_t &rs):
			main_loop_calc(rs)
		{

		}

		/**
		* \brief  Saves base vars
		* \todo   Bad design
		* */
		void
		save_base_vars ()
		{
			sp_thermal_calc_model_t thermal_calc_model (calc_model_, bs_static_cast());
			thermal_calc_model->thermal_old_data_.save(thermal_calc_model);
			base_t::save_base_vars();
		}

		/**
	    * \brief  Restores base vars
		* \todo   Bad design
		* */
		void
		restore_base_vars ()
		{
			sp_thermal_calc_model_t thermal_calc_model (calc_model_, bs_static_cast());
			thermal_calc_model->thermal_old_data_.restore(thermal_calc_model);
			base_t::restore_base_vars();
	    }

		smart_ptr<fi_operator_impl <strategy_t, is_w, is_g, is_o>, true>
		get_fi_operator(sp_calc_model_t &calc_model, sp_reservoir_t &reservoir, const sp_mesh_iface_t &mesh, sp_jacobian_t &jacobian, sp_jmatrix_t &jmatrix){		
			sp_thermal_calc_model_t thermal_calc_model (calc_model, bs_static_cast());
			smart_ptr <thermal_reservoir_simulator <strategy_t>, true> thermal_rs(rs_, bs_static_cast());
			return new thermal_fi_operator_impl<strategy_t, is_w, is_g, is_o>(thermal_calc_model,calc_model,reservoir, mesh, jacobian, jmatrix, data_map_->dimens, thermal_rs->boundary_builder);
		}
	};
}

#endif //BS_THERMAL_MAIN_LOOP_CALC_H_